<template>
    <div class="commonTreeSelect">
        <van-nav-bar :title="title" @click-left="onClickLeft" left-arrow />

        <div class="header-warp">
            <van-search class="search-input" shape="round" v-model="searchVal" :placeholder="placeholder" />
            <!-- <div class="mode-switch">
                <span class="mode-label">选择模式：</span>
                <van-switch v-model="isMultipleMode" @change="onModeChange" size="20px" active-color="#3772ff" />
                <span class="mode-text">{{ isMultipleMode ? '多选' : '单选' }}</span>
            </div> -->
        </div>

        <div class="tree-wrap">
            <tree
                ref="tree"
                :key="treeDataKey"
                :data="treeData"
                :options="treeOptions"
                :filter="searchVal"
                @node-click="clicktree"
                @click="clicktree"
                @update:selected="clicktree"
            />
        </div>

        <div class="btn-container">
            <div class="btnlist">
                <div class="btn-item" :class="{ activeBtn: type === 1 }" @click="closeBtn">重置</div>
                <div class="btn-item" :class="{ activeBtn2: type === 2 }" @click="submitBtn">确认</div>
            </div>
        </div>
    </div>
</template>

<script>
import backMixin from '../../mixins/backMixin'

export default {
    mixins: [backMixin],
    name: 'assectType',
    data() {
        return {
            searchVal: '',
            mode:'',
            type: 1,
            placeholder:'',
            treeDataKey: 0, // 用于强制树组件重新渲染
            title: '',
            isMultipleMode: false, // 默认单选模式
            singleSelectTimer: null, // 单选模式监听定时器
            treeData: [],
            // 记录已经加载过数据的 key，避免重复请求
            loadedKeys: [],
            treeOptions: {
                propertyNames: {
                    text: 'text',
                    children: 'children',
                    state: 'state'
                },
                filter: {
                    plainList: true
                },
                checkbox: false // 默认不启用复选框（单选）
            }
        }
    },
    created() {
        this.handleRouteKey(this.$route.params.key)

        // 监听路由参数变化并切换数据源（从 Vuex 读取）
        this.$watch(
            () => this.$route.params.key,
            (newKey, oldKey) => {
                if (newKey !== oldKey && typeof this.handleRouteKey === 'function') {
                    this.handleRouteKey(newKey)
                }
            }
        )

        // 监听 Vuex 中各类树数据变化，便于上层页面在跳转前请求并写入 Vuex 后，这里自动更新
        this._unwatchFns = []
        try {
            const store = this.$store
            if (store) {
                this._unwatchFns.push(store.watch(
                    (state) => state.assectData.propertyTypeTree,
                    () => { if (this.mode === 'zclx') this.loadTreeFromStore('zclx') }
                ))
                this._unwatchFns.push(store.watch(
                    (state) => state.assectData.orgTree,
                    () => { if (this.mode === 'gldw') this.loadTreeFromStore('gldw') }
                ))
                this._unwatchFns.push(store.watch(
                    (state) => state.assectData.projectTree,
                    () => { if (this.mode === 'ssxm') this.loadTreeFromStore('ssxm') }
                ))
                this._unwatchFns.push(store.watch(
                    (state) => state.assectData.deptMemberTree,
                    () => { if (this.mode === 'zrr') this.loadTreeFromStore('zrr') }
                ))
                this._unwatchFns.push(store.watch(
                    (state) => state.assectData.deptMemberTree,
                    () => { if (this.mode === 'zcyt') this.loadTreeFromStore('zcyt') }
                ))
            }
        } catch (e) {
            // ignore
        }
    },

    mounted() {
        // 确保树组件渲染后展开节点
        this.$nextTick(() => {
            this.expandTreeNodes()
            // 在单选模式下，监听选中状态变化
            if (!this.isMultipleMode) {
                this.startSingleSelectWatcher()
            }
        })
    },
    watch: {
        isMultipleMode(newVal) {
            // 更新树组件的checkbox配置
            this.treeOptions.checkbox = newVal
            
            if (newVal) {
                // 切换到多选模式，停止单选监听
                this.stopSingleSelectWatcher()
            } else {
                // 切换到单选模式，开始监听
                this.$nextTick(() => {
                    this.startSingleSelectWatcher()
                })
            }
        }
    },
    methods: {
        // 点击或更新节点时的回调（保留入口以便将来扩展）
        clicktree(node){
            // node 可能为树组件传回的节点对象，业务需要时可以在此处理
        },
        handleRouteKey(key) {
            // 根据路由 param 设置当前选择模式（如 zrr/zclx/ssxm/gldw）
            this.mode = key
            // 根据key设置选择模式：只有zrr是多选，其他都是单选
            if (key === 'zrr') {
                this.isMultipleMode = true
                this.title = '选择人员'
                this.placeholder = '搜索人员姓名/分组'
            } else if (key === 'zclx') {
                this.isMultipleMode = false
                this.title = '资产类型'
                this.placeholder = '搜索资产类型/分组'
            } else if (key === 'ssxm') {
                this.isMultipleMode = false
                this.title = '所属项目'
                this.placeholder = '搜索项目名称/分组'
            } else if (key === 'gldw') {
                this.isMultipleMode = false
                this.title = '管理单位'
                this.placeholder = '搜索单位名称/分组'
            }else if (key === 'zcyt') {
                this.isMultipleMode = false
                this.title = '资产用途'
                this.placeholder = '搜索用途名称/分组'
            }

            // 从 Vuex 加载对应树数据（上级页面应在跳转前请求并写入 Vuex）
            this.loadTreeFromStore(key)
            
            // 同步更新树组件的checkbox配置
            this.treeOptions.checkbox = this.isMultipleMode
            // 强制重新渲染树组件
            this.treeDataKey += 1
        },

        // 从 Vuex 读取对应树数据并转换给树组件使用
        loadTreeFromStore(mode) {
            try {
                const store = this.$store.state.assectData
                console.log(store,'store')
                let raw = null
                if (!store) raw = null
                else if (mode === 'zrr') raw = store.deptMemberTree
                else if (mode === 'zclx') raw = store.propertyTypeTree
                else if (mode === 'ssxm') raw = store.projectTree
                else if (mode === 'gldw') raw = store.orgTree
else if (mode === 'zcyt') raw = store.listTree
                if (raw) {
                    const converted = this.convertTreeData(raw, mode === 'ssxm' || mode === 'zcyt' || mode === 'gldw' ? 'ssxm' : 'xzry')
                    this.treeDataKey += 1
                    this.treeData = converted
                    this.$nextTick(() => {
                        this.expandTreeNodes()
                        this.applyInitialSelection()
                    })
                } else {
                    // 没有缓存数据时，不在此页发起网络请求（上级页面应负责）；清空树以避免展示旧数据
                    this.treeDataKey += 1
                    this.treeData = []
                }
            } catch (e) {
                console.warn('loadTreeFromStore error', e)
                this.treeData = []
            }
        },
        // 开始单选模式监听（确保只能选择一个）
        startSingleSelectWatcher() {
            this.stopSingleSelectWatcher() // 先清除之前的定时器
            if (this.isMultipleMode) return
            
            this.singleSelectTimer = setInterval(() => {
                if (!this.isMultipleMode && this.$refs.tree) {
                    const selectedNodes = this.$refs.tree.selected()
                  
                    if (selectedNodes && selectedNodes.tree && selectedNodes.tree.checkedNodes) {
                        const checkedNodes = selectedNodes.tree.checkedNodes
                        if (checkedNodes.length > 1) {
                            // 保留最后一个选中的，取消其他
                            const lastNode = checkedNodes[checkedNodes.length - 1]
                            checkedNodes.forEach((node, index) => {
                                if (index < checkedNodes.length - 1) {
                                    try {
                                        node.uncheck()
                                    } catch (e) {
                                        // 忽略错误
                                    }
                                }
                            })
                        }
                    }
                }
            }, 100) // 每100ms检查一次
        },
        // 停止单选模式监听
        stopSingleSelectWatcher() {
            if (this.singleSelectTimer) {
                clearInterval(this.singleSelectTimer)
                this.singleSelectTimer = null
            }
        },
        //
        // 以下原先在组件内发起的接口请求已迁移到上层页面，结果应写入 Vuex。
        // 组件只从 Vuex 读取数据并展示。
        // 展开树中标记为 expanded 的节点，避免懒加载或折叠影响体验
        expandTreeNodes() {
            if (this.$refs.tree) {
                try {
                    const allNodes = this.$refs.tree.findAll()
                    allNodes.forEach((node) => {
                        if (node && node.data && node.data.state && node.data.state.expanded) {
                            try {
                                node.expand()
                            } catch (e) {
                                console.warn('展开节点失败:', e, node)
                            }
                        }
                    })
                } catch (error) {
                    console.error('展开树节点失败:', error)
                }
            }
        },
        // 根据路由 query 或传入的 backData 做初始回显
        applyInitialSelection() {
            try {
                const q = this.$route && this.$route.query ? this.$route.query : {}
                let parsed = null
                const tryParse = (v) => {
                    if (v == null) return null
                    if (typeof v === 'string') {
                        try { return JSON.parse(v) } catch (e) { return v }
                    }
                    return v
                }

                const keys = ['preselect','selected','selectedIds','value','backData']
                for (const k of keys) {
                    if (q[k]) {
                        parsed = tryParse(q[k])
                        if (parsed) break
                    }
                }

                if (!parsed) return

                let ids = []
                if (Array.isArray(parsed)) {
                    parsed.forEach(item => {
                        if (!item) return
                        const id = item.typeId ?? item.projectId ?? item.orgId ?? item.memberId ?? item.id ?? item.value ?? null
                        if (id !== null && id !== undefined) ids.push(String(id))
                    })
                } else if (typeof parsed === 'object') {
                    const id = parsed.typeId ?? parsed.projectId ?? parsed.orgId ?? parsed.memberId ?? parsed.id ?? parsed.value ?? null
                    if (id !== null && id !== undefined) ids.push(String(id))
                } else if (typeof parsed === 'string' || typeof parsed === 'number') {
                    ids.push(String(parsed))
                }

                if (!ids.length) return

                this.$nextTick(() => {
                    try {
                        if (!this.$refs.tree || !this.$refs.tree.findAll) return
                        const allNodes = this.$refs.tree.findAll() || []
                        allNodes.forEach(node => {
                            if (!node) return
                            const nid = node.id != null ? String(node.id) : (node.data && node.data.id ? String(node.data.id) : null)
                            if (nid && ids.includes(nid)) {
                                try {
                                    if (this.isMultipleMode) {
                                        node.check && node.check()
                                    } else {
                                        node.select && node.select()
                                    }
                                } catch (e) {
                                    // ignore
                                }
                            }
                        })
                    } catch (e) {
                        // ignore
                    }
                })
            } catch (e) {
                // ignore
            }
        },
        getTreeDepth(nodes) {
            if (!Array.isArray(nodes) || nodes.length === 0) return 0
            let maxDepth = 1
            nodes.forEach((node) => {
                if (node.children && Array.isArray(node.children) && node.children.length > 0) {
                    const childDepth = this.getTreeDepth(node.children)
                    maxDepth = Math.max(maxDepth, childDepth + 1)
                }
            })
            return maxDepth
        },
        // 统计树中 member 类型节点数量（递归）
        countMemberNodes(nodes) {
            if (!Array.isArray(nodes) || nodes.length === 0) return 0
            let count = 0
            nodes.forEach((node) => {
                if (node.isMember || node.nodeType === 'Member') {
                    count++
                }
                if (node.children && Array.isArray(node.children) && node.children.length > 0) {
                    count += this.countMemberNodes(node.children)
                }
            })
            return count
        },
        // 将后端返回的数据结构转换为树组件所需格式
        convertTreeData(data,mode) {
            if (!data) return []

            if (typeof data === 'object' && !Array.isArray(data)) {
                if(mode=='xzry'){
                    if (data.newChildList && Array.isArray(data.newChildList)) {
                    return this.convertTreeData(data.newChildList,'xzry')
                }
                }
                if(mode=='ssxm' || mode=='gldw' || mode=='zcyt'){
                    if (data.newChildList && Array.isArray(data.childList)) {
                    return this.convertTreeData(data.childList,'ssxm')
                }
                }
                const converted = this.convertNode(data)
                return converted ? [converted] : []
            }

            if (Array.isArray(data)) {
                return data.map((item) => this.convertNode(item)).filter((item) => item !== null && item !== undefined)
            }

            return []
        },
        // 将单个后端节点转换为树节点格式（包括成员节点）
        convertNode(item) {
            if (!item || typeof item !== 'object') return null

            const orgChildren = item.newChildList || item.childList
            const hasOrgChildren = orgChildren && Array.isArray(orgChildren) && orgChildren.length > 0

            const memberList = item.memberInfoDtoList
            const hasMembers = memberList && Array.isArray(memberList) && memberList.length > 0

            const hasAnyChildren = hasOrgChildren || hasMembers

            const converted = {
                id: item.nodeId || item.id,
                text: item.nodeName || item.text || item.name || '',
                state: item.state || { expanded: hasAnyChildren ? true : false },
                nodeId: item.nodeId,
                nodeName: item.nodeName,
                nodeCode: item.nodeCode,
                parentId: item.parentId,
                nodeType: item.nodeType,
                layer: item.layer
            }

            const allChildren = []

            if (hasOrgChildren) {
                const convertedOrgChildren = orgChildren.map((child) => this.convertNode(child)).filter((child) => child !== null && child !== undefined)
                allChildren.push(...convertedOrgChildren)
            }

            if (hasMembers) {
                const memberNodes = memberList
                    .map((member) => {
                        if (!member || typeof member !== 'object') return null
                        return {
                            id: member.memberId || member.id,
                            text: member.memberName || member.name || '',
                            state: { expanded: false },
                            memberId: member.memberId,
                            memberName: member.memberName,
                            nodeType: 'Member',
                            isMember: true
                        }
                    })
                    .filter((node) => node !== null && node !== undefined)
                allChildren.push(...memberNodes)
            }

            if (allChildren.length > 0) {
                converted.children = allChildren
            }

            return converted
        },
        // 确认按钮：收集选中节点并通过路由回传给调用页（query.backData）
        submitBtn() {
            if (this.$refs.tree) {
                const selectedNodes = this.$refs.tree

                // 获取选中节点
                let arr = []
                if (this.isMultipleMode) {
                    arr = (selectedNodes.tree && selectedNodes.tree.checkedNodes) || []
                } else {
                    const selected = (selectedNodes.tree && selectedNodes.tree.selectedNodes) || []
                    arr = selected.length > 0 ? [selected[0]] : []
                }

                // 如果没有选中任何节点，给出提示并返回
                if (arr.length === 0) {
                    this.$toast && this.$toast('请至少选择一个选项')
                    return
                }

                // 单选模式下，只取最后一个选中的项（保持原有逻辑）
                if (!this.isMultipleMode && arr.length > 1) {
                    arr = [arr[arr.length - 1]]
                }

                let newArr = []
                arr.forEach((node) => {
                    if (this.mode == 'zclx') {
                        newArr.push({ typeId: node.id, typeName: node.data && node.data.text })
                    }
                    if (this.mode == 'ssxm') {
                        newArr.push({ projectId: node.id, projectName: node.data && node.data.text })
                    }
                     if (this.mode == 'zcyt') {
                        newArr.push({ purposeIds: node.id, purposeIdsName: node.data && node.data.text })
                    }
                    if (this.mode == 'gldw') {
                        newArr.push({ orgId: node.id, orgName: node.data && node.data.text })
                    }
                    if (this.mode == 'zrr') {
                        newArr.push({ memberId: node.id, memberName: node.data && node.data.text })
                    }
                })
console.log(newArr,'newArr')
                // 如果有结果，先写入 Vuex（统一结构），再使用统一返回逻辑
                if (newArr.length > 0) {
                    const normalized = newArr.map(item => {
                        const base = { id: item.typeId ?? item.projectId ?? item.orgId ?? item.memberId ?? item.id, text: item.typeName ?? item.projectName ?? item.orgName ?? item.memberName ?? item.text, mode: this.mode }
                        return Object.assign({}, base, item)
                    })

                    // 使用 Vuex 存储返回数据，然后后退到上一页
                    try {
                        this.$store.commit('assectData/setReturnData', newArr)
                        // 如果是人员选择（zrr），同时同步到 selectPersonnel 以兼容已有页面
                        if (this.mode === 'zrr') {
                            this.$store.commit('assectData/setSPersonnel', normalized)
                        }
                    } catch (e) {
                        console.warn('Vuex commit setReturnData failed', e)
                    }
                    this.$router.back()
                }
            }
            this.type = 2
        },
        closeBtn() {
            if (this.$refs.tree) {
                const selectedNodes = this.$refs.tree.selected()
                if (selectedNodes && selectedNodes.tree && selectedNodes.tree.checkedNodes) {
                    const checkedNodes = selectedNodes.tree.checkedNodes
                    checkedNodes.forEach((node) => {
                        try {
                            node.uncheck()
                        } catch (e) {
                            console.warn('取消选中节点失败:', e)
                        }
                    })
                }
            }
            const params = this.$route.params
            // 当用户点击重置时，清理 Vuex 中对应的树缓存，上层页面在下次打开时应重新请求并写入 Vuex
            try {
                if (params.key === 'zrr') {
                    this.$store.commit('assectData/setDeptMemberTree', null)
                    this.loadedKeys = this.loadedKeys.filter(k => k !== 'zrr')
                } else if (params.key === 'zclx') {
                    this.$store.commit('assectData/setPropertyTypeTree', null)
                    this.loadedKeys = this.loadedKeys.filter(k => k !== 'zclx')
                } else if (params.key === 'ssxm') {
                    this.$store.commit('assectData/setProjectTree', null)
                    this.loadedKeys = this.loadedKeys.filter(k => k !== 'ssxm')
                } else if (params.key === 'gldw') {
                    this.$store.commit('assectData/setOrgTree', null)
                    this.loadedKeys = this.loadedKeys.filter(k => k !== 'gldw')
                } else if (params.key === 'zcyt') {
                    this.$store.commit('assectData/setlistTree', null)
                    this.loadedKeys = this.loadedKeys.filter(k => k !== 'zcyt')
                }
            } catch (e) {
                console.warn('清理 Vuex 树缓存失败', e)
            }
        },
        onClickLeft() {
            this.$router.back()
        }
    },
    beforeDestroy() {
        this.stopSingleSelectWatcher()
        this.treeData = []
        this.searchVal = ''
        this.type = 1
        this.treeDataKey = 0
        this.title = ''
        // 取消 Vuex 监听
        try {
            if (this._unwatchFns && Array.isArray(this._unwatchFns)) {
                this._unwatchFns.forEach(fn => {
                    try { fn() } catch (e) { /* ignore */ }
                })
            }
        } catch (e) {}
    }
}
</script>

<style lang="less" scoped>
::v-deep .tree-checkbox.indeterminate{
    background:#3772ff;
    border: #3772ff;
    border-radius: 50%;
}
::v-deep .tree-checkbox.checked {
     border-radius: 50%;
    }
/* 样式保持不变 */
.commonTreeSelect {
    width: 100%;
    height: 100vh;
    background-color: #fff;
    display: flex;
    flex-direction: column;
    position: relative;

    .header-warp {
        width: 100%;
        padding: 10px 12px;
        
        .mode-switch {
            display: flex;
            align-items: center;
            margin-top: 10px;
            padding: 8px 12px;
            background-color: #f5f5f5;
            border-radius: 6px;
            
            .mode-label {
                font-size: 14px;
                color: #666;
                margin-right: 8px;
            }
            
            .mode-text {
                font-size: 14px;
                color: #333;
                margin-left: 8px;
                font-weight: 500;
            }
        }
    }

    .tree-wrap {
        flex: 1;
        overflow: hidden;
        padding: 0 12px;

        /deep/ .tree {
            width: 100%;
            height: 70vh;
            overflow-y: auto;

            ul {
                list-style: none;
                padding: 0;
                margin: 0;

                li {
                    padding: 8px 0;

                    .tree-anchor {
                        font-size: 14px;
                        color: #333;
                        padding: 0;
                        display: flex;
                        align-items: center;
                        min-height: 32px;
                    }

                    .tree-arrow {
                        margin-right: 8px;
                    }

                    .tree-checkbox {
                        margin-right: 8px;
                        cursor: pointer;
                        display: inline-flex;
                        align-items: center;
                        border-radius: 50%;
                        width: 18px !important;
                        height: 18px !important;
                        input[type='checkbox'] {
                            width: 18px;
                            height: 18px;
                            cursor: pointer;
                            margin: 0;
                            vertical-align: middle;
                            -webkit-appearance: none;
                            appearance: none;
                            border: 1px solid #dcdfe6;
                            border-radius: 50%; /* 圆形 */
                            background-color: #fff;
                            position: relative;

                            &:checked {
                                background-color: #3772ff;
                                border-color: #3772ff;

                                &::after {
                                    content: '';
                                    position: absolute;
                                    /* 调整为圆形内的对勾位置 */
                                    left: 5px;
                                    top: 0px;
                                    width: 6px;
                                    height: 11px;
                                    border: solid #fff;
                                    border-width: 0 2px 2px 0;
                                    transform: rotate(45deg);
                                    display: block;
                                }
                            }
                        }
                        /* 有些树实现不使用原生 checkbox，而是用 .tree-checkbox 元素本身表示状态，下面补充通用样式以覆盖此类实现 */
                        &.checked,
                        &.is-checked {
                            background-color: #3772ff;
                            border-color: #3772ff;
                        }
                        &.checked::after,
                        &.is-checked::after {
                            content: '';
                            position: absolute;
                            left: 5px;
                            top: 2px;
                            width: 6px;
                            height: 11px;
                            border: solid #fff;
                            border-width: 0 2px 2px 0;
                            transform: rotate(45deg);
                            display: block;
                        }
                    }
                    
                    .tree-anchor {
                        &.selected {
                            color: #3772ff;
                            font-weight: 500;
                        }
                    }
                }
            }
        }
    }

    .btn-container {
        position: absolute;
        bottom: 100px;
        left: 50%;
        transform: translateX(-50%);
        width: 100%;
        display: flex;
        justify-content: center;
        padding: 0 20px;
    }

    .btnlist {
        display: flex;
        border: 1px solid #3772ff;
        background-color: #3772ff;
        border-radius: 12.5px;
        width: 305px;
        overflow: hidden;
    }

    .btn-item {
        flex: 1;
        padding: 12px;
        text-align: center;
        color: #fff;
        font-size: 14px;
        cursor: pointer;
        transition: all 0.3s;
    }

    .activeBtn {
        border-radius: 12.5px 0 17.5px 12.5px;
        background-color: #fff;
        color: #000;
    }

    .activeBtn2 {
        border-radius: 0 12.5px 12.5px 17.5px;
        background-color: #fff;
        color: #000;
    }
}
::v-deep .tree-checkbox.checked::after {
    left: 4px;
    top: 0px;
}
</style>